#include "general.h"
#if (SENSOR_TYPE == Sensor_OV3630)
#include "pv_api.h"
#include "sensor_cdsp.h"
#include "sp1k_aaa_api.h"
#define HAL_FRONT_REMOVE_UNCALL_FUNCTION

UINT8 sensorDriverGainClass = 0xff;
UINT8	RawR[256],RawG[256],RawB[256];
UINT8 last_gain;
UINT32 last_shutter;

#define MAX_FRAME_RATE_30_IDX 120	// New limited for OV3630 - Jim@0424
#define MIN_FRAME_RATE_30_IDX 13	// New limited for OV3630 - Jim@0424
#define MAX_FRAME_RATE_15_IDX 120	// New limited for OV3630 - Jim@0424
#define MIN_FRAME_RATE_15_IDX 13	// New limited for OV3630 - Jim@0424
// New AE table for OV3630 turnkey - Jim@0424
code AEstr LVtbl60[121] =
	{	{	50	,	300	,	46	,	0	}	,
		{	51	,	300	,	46	,	0	}	,
		{	52	,	300	,	46	,	0	}	,
		{	53	,	300	,	46	,	0	}	,
		{	54	,	300	,	46	,	0	}	,
		{	55	,	300	,	46	,	0	}	,
		{	56	,	300	,	46	,	0	}	,
		{	57	,	300	,	46	,	0	}	,
		{	58	,	300	,	46	,	0	}	,
		{	59	,	300	,	46	,	0	}	,
		{	60	,	300	,	46	,	0	}	,
		{	61	,	300	,	46	,	0	}	,
		{	62	,	300	,	46	,	0	}	,
		{	63	,	300	,	46	,	0	}	,
		{	64	,	300	,	46	,	0	}	,
		{	65	,	300	,	45	,	0	}	,
		{	66	,	300	,	43	,	0	}	,
		{	67	,	300	,	42	,	0	}	,
		{	68	,	300	,	40	,	0	}	,
		{	69	,	300	,	38	,	0	}	,
		{	70	,	300	,	37	,	0	}	,
		{	71	,	300	,	35	,	0	}	,
		{	72	,	300	,	34	,	0	}	,
		{	73	,	300	,	32	,	0	}	,
		{	74	,	300	,	31	,	0	}	,
		{	75	,	300	,	29	,	0	}	,
		{	76	,	300	,	27	,	0	}	,
		{	77	,	300	,	25	,	0	}	,
		{	78	,	300	,	23	,	0	}	,
		{	79	,	300	,	21	,	0	}	,
		{	80	,	300	,	20	,	0	}	,
		{	81	,	300	,	19	,	0	}	,
		{	82	,	300	,	18	,	0	}	,
		{	83	,	300	,	16	,	0	}	,
		{	84	,	300	,	15	,	0	}	,
		{	85	,	300	,	14	,	0	}	,
		{	86	,	300	,	12	,	0	}	,
		{	87	,	300	,	10	,	0	}	,
		{	88	,	300	,	8	,	0	}	,
		{	89	,	400	,	14	,	0	}	,
		{	90	,	400	,	12	,	0	}	,
		{	91	,	400	,	10	,	0	}	,
		{	92	,	400	,	9	,	0	}	,
		{	93	,	400	,	8	,	0	}	,
		{	94	,	600	,	16	,	0	}	,
		{	95	,	600	,	14	,	0	}	,
		{	96	,	600	,	12	,	0	}	,
		{	97	,	600	,	11	,	0	}	,
		{	98	,	600	,	9	,	0	}	,
		{	99	,	600	,	8	,	0	}	,
		{	100	,	1200	,	21	,	0	}	,
		{	101	,	1200	,	20	,	0	}	,
		{	102	,	1200	,	17	,	0	}	,
		{	103	,	1200	,	16	,	0	}	,
		{	104	,	1200	,	15	,	0	}	,
		{	105	,	1200	,	14	,	0	}	,
		{	106	,	1200	,	12	,	0	}	,
		{	107	,	1200	,	10	,	0	}	,
		{	108	,	1200	,	8	,	0	}	,
		{	109	,	1757	,	16	,	0	}	,
		{	110	,	1757	,	15	,	0	}	,
		{	111	,	1757	,	13	,	0	}	,
		{	112	,	1757	,	11	,	0	}	,
		{	113	,	1757	,	10	,	0	}	,
		{	114	,	1757	,	8	,	0	}	,
		{	115	,	1884	,	8	,	0	}	,
		{	116	,	2020	,	8	,	0	}	,
		{	117	,	2165	,	8	,	0	}	,
		{	118	,	2321	,	8	,	0	}	,
		{	119	,	2488	,	8	,	0	}	,
		{	120	,	2667	,	8	,	0	}	,
		{	121	,	2859	,	8	,	0	}	,
		{	122	,	3065	,	8	,	0	}	,
		{	123	,	3286	,	8	,	0	}	,
		{	124	,	3522	,	8	,	0	}	,
		{	125	,	3775	,	8	,	0	}	,
		{	126	,	4047	,	8	,	0	}	,
		{	127	,	4338	,	8	,	0	}	,
		{	128	,	4650	,	8	,	0	}	,
		{	129	,	4984	,	8	,	0	}	,
		{	130	,	5342	,	8	,	0	}	,
		{	131	,	5726	,	8	,	0	}	,
		{	132	,	6138	,	8	,	0	}	,
		{	133	,	6579	,	8	,	0	}	,
		{	134	,	7052	,	8	,	0	}	,
		{	135	,	7559	,	8	,	0	}	,
		{	136	,	8102	,	8	,	0	}	,
		{	137	,	8684	,	8	,	0	}	,
		{	138	,	9308	,	8	,	0	}	,
		{	139	,	9977	,	8	,	0	}	,
		{	140	,	10694	,	8	,	0	}	,
		{	141	,	11462	,	8	,	0	}	,
		{	142	,	12285	,	8	,	0	}	,
		{	143	,	13167	,	8	,	0	}	,
		{	144	,	14113	,	8	,	0	}	,
		{	145	,	15127	,	8	,	0	}	,
		{	146	,	16213	,	8	,	0	}	,
		{	147	,	17377	,	8	,	0	}	,
		{	148	,	18625	,	8	,	0	}	,
		{	149	,	21395	,	8	,	0	}	,
		{	150	,	21395	,	8	,	0	}	,
		{	151	,	22931	,	8	,	0	}	,
		{	152	,	24577	,	8	,	0	}	,
		{	153	,	26341	,	8	,	0	}	,
		{	154	,	28232	,	8	,	0	}	,
		{	155	,	30259	,	8	,	0	}	,
		{	156	,	32431	,	8	,	0	}	,
		{	157	,	34759	,	8	,	0	}	,
		{	158	,	37254	,	8	,	0	}	,
		{	159	,	39928	,	8	,	0	}	,
		{	160	,	42794	,	9	,	0	}	,
		{	161	,	42794	,	8	,	0	}	,
		{	162	,	45866	,	8	,	0	}	,
		{	163	,	49158	,	9	,	0	}	,
		{	164	,	52687	,	8	,	0	}	,
		{	165	,	56469	,	8	,	0	}	,
		{	166	,	60523	,	10	,	0	}	,
		{	167	,	64867	,	8	,	0	}	,
		{	168	,	69523	,	8	,	0	}	,
		{	169	,	74513	,	8	,	0	}	,
		{	170	,	79862	,	10	,	0	}
	}	;

#define MAX_FRAME_RATE_25_IDX 120				//Jim@0516 Update 50Hz AE Table
#define MIN_FRAME_RATE_25_IDX 13				//Jim@0516 Update 50Hz AE Table
#define MAX_FRAME_RATE_12P5_IDX 120				//Jim@0516 Update 50Hz AE Table
#define MIN_FRAME_RATE_12P5_IDX 13				//Jim@0516 Update 50Hz AE Table

code AEstr LVtbl50[121] =					//Jim@0516 Update 50Hz AE Table
		{	{	50	,	333	,	46	,	0	}	,
			{	51	,	333	,	46	,	0	}	,
			{	52	,	333	,	46	,	0	}	,
			{	53	,	333	,	46	,	0	}	,
			{	54	,	333	,	46	,	0	}	,
			{	55	,	333	,	46	,	0	}	,
			{	56	,	333	,	46	,	0	}	,
			{	57	,	333	,	46	,	0	}	,
			{	58	,	333	,	46	,	0	}	,
			{	59	,	333	,	46	,	0	}	,
			{	60	,	333	,	46	,	0	}	,
			{	61	,	333	,	46	,	0	}	,
			{	62	,	333	,	46	,	0	}	,
			{	63	,	333	,	46	,	0	}	,
			{	64	,	333	,	46	,	0	}	,
			{	65	,	333	,	44	,	0	}	,
			{	66	,	333	,	42	,	0	}	,
			{	67	,	333	,	40	,	0	}	,
			{	68	,	333	,	39	,	0	}	,
			{	69	,	333	,	37	,	0	}	,
			{	70	,	333	,	36	,	0	}	,
			{	71	,	333	,	34	,	0	}	,
			{	72	,	333	,	33	,	0	}	,
			{	73	,	333	,	32	,	0	}	,
			{	74	,	333	,	30	,	0	}	,
			{	75	,	333	,	28	,	0	}	,
			{	76	,	333	,	26	,	0	}	,
			{	77	,	333	,	24	,	0	}	,
			{	78	,	333	,	22	,	0	}	,
			{	79	,	333	,	20	,	0	}	,
			{	80	,	333	,	19	,	0	}	,
			{	81	,	333	,	18	,	0	}	,
			{	82	,	333	,	17	,	0	}	,
			{	83	,	333	,	16	,	0	}	,
			{	84	,	333	,	14	,	0	}	,
			{	85	,	333	,	12	,	0	}	,
			{	86	,	333	,	11	,	0	}	,
			{	87	,	333	,	9	,	0	}	,
			{	88	,	333	,	8	,	0	}	,
			{	89	,	500	,	16	,	0	}	,
			{	90	,	500	,	15	,	0	}	,
			{	91	,	500	,	13	,	0	}	,
			{	92	,	500	,	11	,	0	}	,
			{	93	,	500	,	10	,	0	}	,
			{	94	,	500	,	8	,	0	}	,
			{	95	,	500	,	8	,	0	}	,                  //Jim@0521 - AE unstable
			{	96	,	1000	,	21	,	0	}	,
			{	97	,	1000	,	19	,	0	}	,
			{	98	,	1000	,	18	,	0	}	,
			{	99	,	1000	,	17	,	0	}	,
			{	100	,	1000	,	16	,	0	}	,
			{	101	,	1000	,	14	,	0	}	,
			{	102	,	1000	,	10	,	0	}	,
			{	103	,	1000	,	8	,	0	}	,
			{	104	,	1000	,	8	,	0	}	,
			{	105	,	1000	,	8	,	0	}	,
			{	106	,	1005	,	8	,	0	}	,
			{	107	,	1078	,	8	,	0	}	,
			{	108	,	1156	,	8	,	0	}	,
			{	109	,	1240	,	8	,	0	}	,
			{	110	,	1330	,	8	,	0	}	,
			{	111	,	1426	,	8	,	0	}	,
			{	112	,	1529	,	8	,	0	}	,
			{	113	,	1639	,	8	,	0	}	,
			{	114	,	1757	,	8	,	0	}	,
			{	115	,	1884	,	8	,	0	}	,
			{	116	,	2020	,	8	,	0	}	,
			{	117	,	2165	,	8	,	0	}	,
			{	118	,	2321	,	8	,	0	}	,
			{	119	,	2488	,	8	,	0	}	,
			{	120	,	2667	,	8	,	0	}	,
			{	121	,	2859	,	8	,	0	}	,
			{	122	,	3065	,	8	,	0	}	,
			{	123	,	3286	,	8	,	0	}	,
			{	124	,	3522	,	8	,	0	}	,
			{	125	,	3775	,	8	,	0	}	,
			{	126	,	4047	,	8	,	0	}	,
			{	127	,	4338	,	8	,	0	}	,
			{	128	,	4650	,	8	,	0	}	,
			{	129	,	4984	,	8	,	0	}	,
			{	130	,	5342	,	8	,	0	}	,
			{	131	,	5726	,	8	,	0	}	,
			{	132	,	6138	,	8	,	0	}	,
			{	133	,	6579	,	8	,	0	}	,
			{	134	,	7052	,	8	,	0	}	,
			{	135	,	7559	,	8	,	0	}	,
			{	136	,	8102	,	8	,	0	}	,
			{	137	,	8684	,	8	,	0	}	,
			{	138	,	9308	,	8	,	0	}	,
			{	139	,	9977	,	8	,	0	}	,
			{	140	,	10694	,	8	,	0	}	,
			{	141	,	11462	,	8	,	0	}	,
			{	142	,	12285	,	8	,	0	}	,
			{	143	,	13167	,	8	,	0	}	,
			{	144	,	14113	,	8	,	0	}	,
			{	145	,	15127	,	8	,	0	}	,
			{	146	,	16213	,	8	,	0	}	,
			{	147	,	17377	,	8	,	0	}	,
			{	148	,	18625	,	8	,	0	}	,
			{	149	,	21395	,	8	,	0	}	,
			{	150	,	21395	,	8	,	0	}	,
			{	151	,	22931	,	8	,	0	}	,
			{	152	,	24577	,	8	,	0	}	,
			{	153	,	26341	,	8	,	0	}	,
			{	154	,	28232	,	8	,	0	}	,
			{	155	,	30259	,	8	,	0	}	,
			{	156	,	32431	,	8	,	0	}	,
			{	157	,	34759	,	8	,	0	}	,
			{	158	,	37254	,	8	,	0	}	,
			{	159	,	39928	,	8	,	0	}	,
			{	160	,	42794	,	9	,	0	}	,
			{	161	,	42794	,	8	,	0	}	,
			{	162	,	45866	,	8	,	0	}	,
			{	163	,	49158	,	9	,	0	}	,
			{	164	,	52687	,	8	,	0	}	,
			{	165	,	56469	,	8	,	0	}	,
			{	166	,	60523	,	10	,	0	}	,
			{	167	,	64867	,	8	,	0	}	,
			{	168	,	69523	,	8	,	0	}	,
			{	169	,	74513	,	8	,	0	}	,
			{	170	,	79862	,	10	,	0	}
		}	;

#define MAX_GAIN_IDX (46)
#define MIN_GAIN_IDX 5

code UINT8 gaintbl[76] = {
	  0,  1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11, 12, 13, 14, 15,
	 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31,
	 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63,
	113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,
	241,242,243,244,245,246,247,248,249,250,251,252,253,254,255};

#define K_GAIN_Large        45
#define K_GAIN_Middle		30
#define K_GAIN_Small		15

code UINT16 cmt[3][9] = {
	{0x0058,0x03D7,0x0011,0x03DF,0x007A,0x03E7,0x03EB,0x03DA,0x007B},
	{0x0045,0x03EF,0x000C,0x03E8,0x006B,0x03EC,0x03F0,0x03F4,0x005C},
	{0x0029,0x0010,0x0006,0x03F4,0x0058,0x03F4,0x03F8,0x0015,0x0033}};

/*
UINT16 ctc_rgain[4]={217,310,384,460};
UINT16 ctc_bgain[4]={402,366,276,219};
*/
//jeff@20080820, some modify in OMG factory.
//UINT16 ctc_rgain[4]={227,320,384,470};
//UINT16 ctc_bgain[4]={412,376,286,229};
//jeff@20080825, some modify in Taipei.
//UINT16 ctc_rgain[4]={248,328,400,0};
//UINT16 ctc_bgain[4]={436,405,289,0};
//jeff@20080825, some modify in Taipei.
//UINT16 ctc_rgain[4]={248,328,400,0};
//UINT16 ctc_bgain[4]={436,405,289,0};
//jeff@20080826, some modify in Taipei.
UINT16 ctc_rgain[4]={243,323,384,0};
UINT16 ctc_bgain[4]={416,400,280,0};




#define MCLKMODE        0 /*mclk mode,'1'from I/O Pad,'0'from internal*/
#define PCLKMODE        1 /*pclk mode,'1'from I/O Pad,'0'from internal*/
#define PREV_MCLKDIV    4 /*MCLK div, master clock = (96MHz / mclkdiv)*/
#define PREV_PCLKDIV    1 /*pixel clock = (master clock) / pclkdiv*/
#define SNAP_MCLKDIV    4 /*MCLK div, master clock = (96MHz / mclkdiv)*/
#define SNAP_PCLKDIV    1 /*pixel clock = (master clock) / pclkdiv*/
#if (PCLKMODE == 1)
#define PREV_PCLKFREQ (UINT32) 27600000
#define SNAP_PCLKFREQ (UINT32) 24000000
#define CLK_RATIO     (UINT8) ((SNAP_PCLKFREQ/1000) * 128 / (PREV_PCLKFREQ/1000))
#else
#define PREV_PCLKFREQ (UINT32) 96000000 / PREV_MCLKDIV / PREV_PCLKDIV
#define SNAP_PCLKFREQ (UINT32) 96000000 / SNAP_MCLKDIV / SNAP_PCLKDIV
#define CLK_RATIO     (UINT8) ((UINT16) PREV_MCLKDIV * PREV_PCLKDIV * 128 / SNAP_MCLKDIV / SNAP_PCLKDIV)
#endif
#define PCLKphase 0
#define TGGPIOFUNC 0
#define TGGPIODIR 0x04
#define TGGPIOVAL 0

xdata UINT16 exptime;
extern xdata UINT32 G_SHUTTER;
extern xdata UINT8 G_GAIN;
extern xdata UINT8 PreGain;
extern xdata UINT32 PreShutter;
extern UINT8 HAL_CDSPeofWait( UINT8 Number);
extern void cdspColorMatrixRestore_Intr(void);
extern void cdspColorMatrixRestore(void);

void  HAL_OVI2C_Write(UINT8 RegAddr, UINT8 RegData)
{
	UINT8 reg_addr[1], reg_data[1];
	reg_addr[0] = RegAddr;
 	reg_data[0] = RegData;
 	HAL_WriteSSC(reg_addr, reg_data, 0x01, 0x00);  //Set Seq SSC Write
}

void  HAL_FrontInit (UINT8 CamMode) USING_0
{
	UINT8 tmp0;
	printf (" Initialize the Front Sensor_OV36320 : Enter !!,CamMode=%d \n",CamMode);

	HAL_SetFrontIOConfig(TGGPIOFUNC, 0x00, TGGPIODIR, TGGPIOVAL);
	HAL_SetFrontCLKSource(MCLKMODE, PCLKMODE);
	HAL_SetFrontCLKSet(PREV_MCLKDIV, PREV_PCLKDIV, 0);
	tmp0 = XBYTE[0x20E4];
	tmp0 &= 0xF0;
	tmp0 |= PCLKphase;
	XBYTE[0x20E4] |= tmp0;
	HAL_SSCConfig(Sensor_Slave_Address, Sensor_SSC_Freq);
	XBYTE[0x2AB0] = 0x01;		      //Reset Sensor interface
	XBYTE[0x2AB0] = 0x00;
	HAL_SensorRegInit();
}

void  HAL_FrontPreviewSet(void) USING_0
{
	HAL_FrontVdWait(0,1);
	HAL_SetFrontCLKSource(MCLKMODE, PCLKMODE);
	HAL_SetFrontCLKSet(PREV_MCLKDIV, PREV_PCLKDIV, 0);
	HAL_SetFrontImgCrop(Sensor_Preview_HOffset, Sensor_Preview_VOffset, Sensor_Preview_HSize, Sensor_Preview_VSize, 0x00);
	HAL_SetFrontInverse(Prev_Hsync_Inverse,Prev_Vsync_Inverse);
	HAL_SetFrontReshape(Sensor_Preview_Hfall, Sensor_Preview_Hrise, Sensor_Preview_HReshen, Sensor_Preview_Vfall, Sensor_Preview_Vrise, Sensor_Preview_VReshen);
	HAL_SetSensorPreview();
	XBYTE[0x2110]=Sensor_Preview_BayerPattern;
}
void  HAL_FrontSnapSet(UINT16 Hsize,UINT16 Vsize) USING_0
{
	HAL_SetFrontCLKSet(SNAP_MCLKDIV, SNAP_PCLKDIV, 0);
	HAL_SetFrontReshape(Sensor_Snap_Hfall, Sensor_Snap_Hrise, Sensor_Snap_HReshen, Sensor_Snap_Vfall, Sensor_Snap_Vrise, Sensor_Snap_VReshen);
	HAL_SetFrontImgCrop(Sensor_Snap_HOffset, Sensor_Snap_VOffset, Hsize, Vsize, 1);
	//HAL_SetFrontInverse(Snap_Hsync_Inverse,Snap_Vsync_Inverse);
	XBYTE[0x2110]=Sensor_Snap_BayerPattern;
	PreGain =0;
	PreShutter = 0;
}
void  HAL_SensorRegInit(void)
{
	HAL_Wait(20);
	HAL_OVI2C_Write(0x12,0x80);
  	HAL_Wait(300);
	HAL_OVI2C_Write(0x3c, 0xb7);
	HAL_OVI2C_Write(0x3c, 0x37);
	HAL_OVI2C_Write(0x0e, 0x19);
	HAL_OVI2C_Write(0x14, 0x98);
	HAL_OVI2C_Write(0x33, 0x38);
	HAL_OVI2C_Write(0x34, 0x20);
	HAL_OVI2C_Write(0x37, 0x81);
	HAL_OVI2C_Write(0x44, 0x00);
	HAL_OVI2C_Write(0x11, 0x40);
	HAL_OVI2C_Write(0x39, 0x02);
	HAL_OVI2C_Write(0x4a, 0x0a);
	HAL_OVI2C_Write(0x03, 0x0f);
	HAL_OVI2C_Write(0x48, 0x80);
	HAL_OVI2C_Write(0x21, 0x90);
	HAL_OVI2C_Write(0x42, 0x03);
	HAL_OVI2C_Write(0x5c, 0x40);
	HAL_OVI2C_Write(0x60, 0x06);
	HAL_OVI2C_Write(0x1e, 0xc0);
	HAL_OVI2C_Write(0x36, 0x12);
	HAL_OVI2C_Write(0x51, 0x00);
	HAL_OVI2C_Write(0x52, 0x40);
	HAL_OVI2C_Write(0x59, 0x00);
	HAL_OVI2C_Write(0x7e, 0x08);
	HAL_OVI2C_Write(0x53, 0x10);
	HAL_OVI2C_Write(0x59, 0x01);
	HAL_OVI2C_Write(0x7e, 0x20);
	HAL_OVI2C_Write(0x59, 0x02);
	HAL_OVI2C_Write(0x7e, 0x03);
	HAL_OVI2C_Write(0x54, 0x08);
	HAL_OVI2C_Write(0x55, 0x85);
	HAL_OVI2C_Write(0x58, 0xc1);
	HAL_OVI2C_Write(0x56, 0x28);
	HAL_OVI2C_Write(0x20, 0x80);
	HAL_OVI2C_Write(0x28, 0x30);
	HAL_OVI2C_Write(0x6d, 0x00);
	HAL_OVI2C_Write(0x6e, 0x00);
	HAL_OVI2C_Write(0x68, 0x00);
	HAL_OVI2C_Write(0x69, 0x00);
	HAL_OVI2C_Write(0x6a, 0x00);
	HAL_OVI2C_Write(0x6b, 0x00);
	HAL_OVI2C_Write(0x70, 0x01);
	HAL_OVI2C_Write(0x71, 0x94);
	HAL_OVI2C_Write(0x73, 0xc1);
	HAL_OVI2C_Write(0x36, 0x40);
	HAL_OVI2C_Write(0x3e, 0x60);
	HAL_OVI2C_Write(0x41, 0x40);
	HAL_OVI2C_Write(0x6c, 0x00);
	HAL_OVI2C_Write(0x70, 0x02);
	HAL_OVI2C_Write(0x71, 0x94);
	HAL_OVI2C_Write(0x1B, 0x02);
	HAL_OVI2C_Write(0x13, 0x80);
	HAL_OVI2C_Write(0x01, 0x80);
	HAL_OVI2C_Write(0x02, 0x80);
	HAL_OVI2C_Write(0x16, 0x80);
	HAL_OVI2C_Write(0x43, 0x84);
	HAL_OVI2C_Write(0x38, 0xa4);
}

void HAL_SetSensorPreview(void) USING_0
{
	HAL_OVI2C_Write(0x3c, 0xb7);
	HAL_OVI2C_Write(0x3c, 0x37);
	HAL_OVI2C_Write(0x11, 0x40);
	HAL_OVI2C_Write(0x12, 0x40);
	HAL_OVI2C_Write(0x0d, 0x26);
	HAL_OVI2C_Write(0x17, 0x10);
	HAL_OVI2C_Write(0x18, 0x50);
	HAL_OVI2C_Write(0x19, 0x00);
	HAL_OVI2C_Write(0x1a, 0x60);
	HAL_OVI2C_Write(0x32, 0xa4);
	HAL_OVI2C_Write(0x15, 0x42);
	HAL_OVI2C_Write(0x43, 0x84);
	HAL_OVI2C_Write(0x38, 0xa4);
	HAL_OVI2C_Write(0x18, 0x01);
	HAL_OVI2C_Write(0x03, 0x0f);
	HAL_OVI2C_Write(0x2b, 0x00);
	HAL_OVI2C_Write(0x3d, 0x25);
	HAL_OVI2C_Write(0x2d, 0x00);
	HAL_OVI2C_Write(0x2e, 0x00);
	HAL_OVI2C_Write(0x45, 0x00);
}
/**************************************************************************************
*                                                                                     *
*  Function Name : HAL_FrontGainSet                                                     *
*                                                                                     *
*  Purposes      :                                                                    *
*    To control Sensor gain                                                           *
*                                                                                     *
*  Desprictions  :                                                                    *
*    Adjust gain value for sensor                                                     *
*                                                                                     *
*  Arguments     :                                                                    *
*    value : in, gain value to set                                                    *
*    option : in, 0 -> immediate change value                                         *
*                 1 -> synchronize the value to the next Vsync                        *
*                                                                                     *
*  Returns       :                                                                    *
*    Error message                                                                    *
*                                                                                     *
*  See also      :                                                                    *
*                                                                                     *
***************************************************************************************/
UINT8 HAL_FrontGainSet(
    UINT32 value,
    UINT32  option
)USING_1
{
	UINT32 tmp0;
	UINT8 regaddr[1], regdata[1];

	tmp0 = option & 0x01;
	regaddr[0] = 0x00;
	regdata[0] = gaintbl[(UINT8) value];
	HAL_WriteSSC(regaddr, regdata, 0x01, 0);
	last_gain= regdata[0] ;
	return SUCCESS;
}

UINT8 HAL_FrontGainSet_Intr(
    UINT32 value,
    UINT32  option
)USING_1
{
	UINT32 tmp0;
	UINT8 regaddr[1], regdata[1];

	tmp0 = option & 0x01;
	regaddr[0] = 0x00;
	regdata[0] = gaintbl[(UINT8) value];
	HAL_WriteSSC_Intr(regaddr, regdata, 0x01, 0);
	last_gain= regdata[0] ;
	return SUCCESS;
}

/**************************************************************************************
*                                                                                     *
*  Function Name : HAL_FrontExpTimeSet                                                  *
*                                                                                     *
*  Purposes      :                                                                    *
*    To control exposure time                                                         *
*                                                                                     *
*  Desprictions  :                                                                    *
*    Adjust exposure time value                                                       *
*                                                                                     *
*  Arguments     :                                                                    *
*    value : in, expossure time value to set, unit 0.1ms                              *
*    option : in, 0 -> immediate change value                                         *
*                 1 -> synchronize the value to the next Vsync                        *
*                                                                                     *
*  Returns       :                                                                    *
*    Error message                                                                    *
*                                                                                     *
*  See also      :                                                                    *
*                                                                                     *
***************************************************************************************/
UINT32
HAL_FrontExpTimeSet(
	UINT32 value,
	UINT32 option
) USING_1
{
	UINT16 ltotal, ftotal, espline;
	UINT32 pixclk;
	UINT8  regaddr[2], regdata[2];

	ltotal = Sensor_Preview_LineTotal;	/* Read line total */
	ftotal = Sensor_Preview_FrameTotal; /* Read frame total */
	pixclk = PREV_PCLKFREQ;
	last_shutter=value;

	espline = (pixclk * 10) / (ltotal * value);
	option = option & 0x01;

	regaddr[0] = 0x10;
	regdata[0] = (espline >> 2)&0xff;
	regaddr[1] = 0x04;
	regdata[1] = (0x24|(espline & 0x03)) ;
	HAL_WriteSSC(regaddr, regdata, 0x02, option | 0x02);
	return SUCCESS;
}

UINT32
HAL_FrontExpTimeSet_Intr(
	UINT32 value,
	UINT32 option
) USING_1
{
	UINT16 ltotal, ftotal, espline;
	UINT32 pixclk;
	UINT8  regaddr[2], regdata[2];

	ltotal = Sensor_Preview_LineTotal;	/* Read line total */
	ftotal = Sensor_Preview_FrameTotal; /* Read frame total */
	pixclk = PREV_PCLKFREQ;
	last_shutter=value;

	espline = (pixclk * 10) / (ltotal * value);
	option = option & 0x01;

	regaddr[0] = 0x10;
	regdata[0] = (espline >> 2)&0xff;
	regaddr[1] = 0x04;
	regdata[1] = (0x24|(espline & 0x03)) ;
	HAL_WriteSSC_Intr(regaddr, regdata, 0x02, option | 0x02);
	return SUCCESS;
}

/**************************************************************************************
*                                                                                     *
*  Function Name : HAL_FrontFrameRateSet                                                *
*                                                                                     *
*  Purposes      :                                                                    *
*    To control Frame Rate                                                            *
*                                                                                     *
*  Desprictions  :                                                                    *
*    Adjust Frame rate for sensor                                                     *
*                                                                                     *
*  Arguments     :                                                                    *
*    value : in, frame rate value to set                                              *
*    option : in, 0 -> immediate change value                                         *
*                 1 -> synchronize the value to the next Vsync                        *
*                                                                                     *
*  Returns       :                                                                    *
*    Error message                                                                    *
*                                                                                     *
*  See also      :                                                                    *
*                                                                                     *
***************************************************************************************/

UINT32
HAL_FrontFrameRateSet(
    UINT32 value,
    UINT32 option
)
{
	value = value;
	option = option;
#if 0
	UINT32 ltotal, ftotal;
	UINT32 pixclk, tmp0;

	UINT8 regaddr[4], regdata[4];

	ltotal = Sensor_Preview_LineTotal;	/* Read line total */
	ftotal = Sensor_Preview_FrameTotal; /* Read frame total */

	pixclk = PREV_PCLKFREQ;
	option = option & 0x01;

	tmp0=(pixclk * 10) /(ltotal * value);

	if (tmp0 >= ftotal ) {
		tmp0 =tmp0-ftotal;
	}
	else {
	    tmp0 =0;
	};
	regaddr[0] = 0x46;//0x2D;
	regdata[0] = tmp0;
	regaddr[1] = 0x47;//0x2E;
	regdata[1] = tmp0 >> 8;
	HAL_WriteSSC(regaddr, regdata, 0x02, option | 0x02);
#endif
	return 0;
}

void HAL_ExpTransToSnap(void)
{

	UINT16 ltotal, ftotal,espline;
	UINT32 tmp0,pixclk;
	UINT8  regaddr[7], regdata[7];
	UINT8  s_gain,lastt_gain;

	ltotal = Sensor_Snap_LineTotal;						/* Read line total */
	ftotal = Sensor_Snap_FrameTotal;					/* Read frame total */
	pixclk = SNAP_PCLKFREQ;

	espline = (pixclk * 20) / (ltotal * last_shutter);
	s_gain = last_gain;

	if (s_gain >= 0x30)
	{
		lastt_gain = s_gain - 32;
		espline = espline*2;
	}
	else if (s_gain >= 0x10)
	{
		lastt_gain = s_gain - 16;
		espline = espline*2;
	}
	else
	{
		lastt_gain=s_gain;
		espline=espline;
	}

	cdspColorMatrixRestore();
	XBYTE[0x21D3] = 0x02;
	XBYTE[0x21D0] = 0x02;
	sensorDriverGainClass = 0;

	if (espline >= ftotal ) {
		tmp0 =espline-ftotal;
		espline = ftotal-1;
	}
	else {
		tmp0 =0;
	};
	regaddr[0] = 0x10;
	regdata[0] = (espline >> 2)&0xff;
	regaddr[1] = 0x04;
	regdata[1] = (0x24|(espline & 0x03));
	regaddr[2] = 0x45;
	regdata[2] = (espline >>10)&0x3f ;
	regaddr[3] = 0x2D;
	regdata[3] = tmp0;
	regaddr[4] = 0x2E;
	regdata[4] = tmp0 >> 8;
	regaddr[5] = 0x00;
	regdata[5] = lastt_gain;
	HAL_WriteSSC(regaddr, regdata, 0x06,  0x02);
}

UINT8 HAL_SnapRaw8(UINT8 mode, UINT8 opt) USING_0
{
    	//UINT8  regaddr[7], regdata[7];
		//UINT16 i;
	mode = mode;

	if( opt == 1 ) {
		HAL_FrontVdWait(1,1);

		HAL_OVI2C_Write(0x12, 0x00);
		HAL_OVI2C_Write(0x17, 0x11);
		HAL_OVI2C_Write(0x11, 0x00);
		HAL_OVI2C_Write(0x18, 0x00);
		HAL_OVI2C_Write(0x19, 0x01);
		HAL_OVI2C_Write(0x1a, 0xc2);
		HAL_OVI2C_Write(0x03, 0x03);
		HAL_OVI2C_Write(0x2b, 0x20);
		HAL_OVI2C_Write(0x32, 0x34);
		HAL_OVI2C_Write(0x38, 0xa0);
		HAL_OVI2C_Write(0x3d, 0x31);
		#if 0
		HAL_OVI2C_Write(0x45, 0x00);
		HAL_OVI2C_Write(0x2d, 0x00);
		HAL_OVI2C_Write(0x2e, 0x00);
		HAL_OVI2C_Write(0x10, aaaaa);
		HAL_OVI2C_Write(0x00, ggggg);
		printf("%bu-----%bu----/n",aaaaa,ggggg);
		#else
		HAL_ExpTransToSnap();
		#endif
	}

	HAL_FrontVdWait(0,1); // 20081024 mantis 32544 wenguo
	HAL_CdspWriteSkip( 6, 1 );
	HAL_FrontVdWait(0,1);
	HAL_FrontVdWait(1,1);
	HAL_FrontInputGate(0x11);
	HAL_CDSPeofWait(1);
	return 0;
}

#ifndef HAL_FRONT_REMOVE_UNCALL_FUNCTION
void HalSensorPrePV(
	void
)
{
	HAL_OVI2C_Write(0x3d, 0x31);
	HAL_OVI2C_Write(0x2d, 0x00);
	HAL_OVI2C_Write(0x2E, 0x00);
	HAL_FrontVdWait(0,1);
	HAL_FrontVdWait(0,1);
	return;
}
#endif

#if 1 /*cs added for gain*/
UINT8 HAL_MaxGainIndexGet()
{
	return(MAX_GAIN_IDX);
}
UINT8 HAL_MinGainIndexGet()
{
	return(MIN_GAIN_IDX);
}

UINT8 HAL_MaxExpIndexGet(
UINT16 frame
)
{
	switch (frame) {
		case SP1K_FRAME_RATE_30:
			return(MAX_FRAME_RATE_30_IDX);
			break;
		case SP1K_FRAME_RATE_15:
			return(MAX_FRAME_RATE_15_IDX);
			break;
		case SP1K_FRAME_RATE_25:
			return(MAX_FRAME_RATE_25_IDX);
			break;
		case SP1K_FRAME_RATE_12P5:
			return(MAX_FRAME_RATE_12P5_IDX);
			break;
		default:
			return FAIL;
	};
}

UINT8 HAL_MinExpIndexGet(
UINT16 frame
)
{
	switch (frame) {
		case SP1K_FRAME_RATE_30:
			return(MIN_FRAME_RATE_30_IDX);
			break;
		case SP1K_FRAME_RATE_15:
			return(MIN_FRAME_RATE_15_IDX);
			break;
		case SP1K_FRAME_RATE_25:
			return(MIN_FRAME_RATE_25_IDX);
			break;
		case SP1K_FRAME_RATE_12P5:
			return(MIN_FRAME_RATE_12P5_IDX);
			break;
		default:
			return FAIL;
	};
}

void HAL_ColorSatReduce_Intr(UINT8 idx)	   // reduce color saturation and edge
{

	//HAL_CdspColorMSet_Intr(0x059,(0x1d3+512),0x013,(0x1d7+512),0x079,(0x1ee+512),(0x1e5+512),(0x1cd+512),0x08b);
	//XBYTE[0x21D3] = 0x06;
	//XBYTE[0x21D0] = 0x08;
#if 1
	if(idx > K_GAIN_Large) {
		if( sensorDriverGainClass != 3 ) {
			HAL_CdspColorMSet_Intr(cmt[2][0],cmt[2][1],cmt[2][2],cmt[2][3],cmt[2][4],cmt[2][5],cmt[2][6],cmt[2][7],cmt[2][8]);
			XBYTE[0x21D3] = 0x08;
			XBYTE[0x21D0] = 0x08;

			sensorDriverGainClass = 3;
		}
	}
	else if (idx > K_GAIN_Middle) {
		if( sensorDriverGainClass != 2 ) {
			HAL_CdspColorMSet_Intr(cmt[1][0],cmt[1][1],cmt[1][2],cmt[1][3],cmt[1][4],cmt[1][5],cmt[1][6],cmt[1][7],cmt[1][8]);
			XBYTE[0x21D3] = 0x06;
			XBYTE[0x21D0] = 0x08;

			sensorDriverGainClass = 2;
		}
	}
	else if (idx > K_GAIN_Small) {
		if( sensorDriverGainClass != 1 ) {
			HAL_CdspColorMSet_Intr(cmt[0][0],cmt[0][1],cmt[0][2],cmt[0][3],cmt[0][4],cmt[0][5],cmt[0][6],cmt[0][7],cmt[0][8]); // for hgnoise
			XBYTE[0x21D3] = 0x04;
			XBYTE[0x21D0] = 0x0A;

			sensorDriverGainClass = 1;
		}
	}
	else {
		if( sensorDriverGainClass != 0 ) {
			cdspColorMatrixRestore_Intr();
			XBYTE[0x21D3] = 0x02;
			XBYTE[0x21D0] = 0x02;

			sensorDriverGainClass = 0;
		}
	};
#endif
}
#endif
#endif
